import jwt

from rest_framework.exceptions import AuthenticationFailed
from rest_framework.authentication import BaseAuthentication
from rest_framework_jwt.settings import api_settings

from .models import User


jwt_decode_handler = api_settings.JWT_DECODE_HANDLER


class JWTAuthentication(BaseAuthentication):
    def authenticate(self, request):
        token = request.META.get('HTTP_TOKEN')
        # 背过
        # 校验token是否过期，合法，如果都通过，查询出当前用户，返回
        # 如果不通过，抛异常
        try:
            payload = jwt_decode_handler(token)
            print('payload',payload)
            # 如果认证通过，payload就可以认为是安全的，我们就可以使用
            user_id = payload.get('user_id')
            print('user_id',user_id)
            # 每个需要登录后，才能访问的接口，都会走这个认证类，一旦走到这个认证类，机会去数据库查询一次数据，会对数据造成压力？
            user = User.objects.get(pk=user_id)
            # 优化后的
            # user = User(username=payload.get('username'), id=user_id)
            # user = {'username':payload.get('username'), 'id':user_id}

        except jwt.ExpiredSignature:
            raise AuthenticationFailed('token过期')
        except jwt.DecodeError:
            raise AuthenticationFailed('解码失败')
        except jwt.InvalidTokenError:
            raise AuthenticationFailed('token认证异常')
        except Exception:
            raise AuthenticationFailed('token认证异常')
        return user, token